package com.sdkj.fixed.asset.hc.service;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.StrUtil;
import com.github.pagehelper.PageHelper;
import com.sdkj.fixed.asset.api.hc.vo.in.ReceiptInGetPageParams;
import com.sdkj.fixed.asset.api.hc.vo.out.*;
import com.sdkj.fixed.asset.common.base.BaseMapper;
import com.sdkj.fixed.asset.common.base.BaseService;
import com.sdkj.fixed.asset.common.base.PageParams;
import com.sdkj.fixed.asset.common.exception.LogicException;
import com.sdkj.fixed.asset.common.utils.TimeTool;
import com.sdkj.fixed.asset.hc.controller.CategoryController;
import com.sdkj.fixed.asset.hc.mapper.*;
import com.sdkj.fixed.asset.hc.util.CacheUtil;
import com.sdkj.fixed.asset.pojo.hc.*;
import com.sdkj.fixed.asset.pojo.system.UserDateAuth;
import com.sdkj.fixed.asset.pojo.system.UserManagement;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import tk.mybatis.mapper.entity.Example;

import javax.annotation.Resource;
import javax.persistence.Transient;
import javax.servlet.http.HttpServletRequest;
import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;

/***
 *
 * @author scx
 *
 */
@Service
public class ReceiptInService extends BaseService<ReceiptIn> {

    private static Logger log = LoggerFactory.getLogger(ReceiptInService.class);

    @Resource
    private ReceiptInMapper mapper;

    @Resource
    private ProductMapper productMapper;

    @Resource
    private ReceiptInProductMapper receiptInProductMapper;

    @Resource
    private CategoryMapper categoryMapper;

    @Resource
    private CategoryProductMapper categoryProductMapper;

    @Resource
    private CategoryService categoryService;

    @Resource
    private UserDataAuthMapper userDataAuthMapper;

    @Resource
    private UserManagementMapper userManagementMapper;

    @Resource
    private SetManagementMapper setManagementMapper;

    @Override
    public BaseMapper<ReceiptIn> getMapper() {
        return mapper;
    }

    @Resource
    private HttpServletRequest request;

    @Resource
    private CacheUtil cacheUtil;

    @Resource
    private QwertMapper qwertMapper;

    private void qwertyu(CategoryProduct categoryProduct, ReceiptInProduct receiptInProduct) {
        if (categoryProduct.getProductNum() == null) {
            categoryProduct.setTotalPrice("0.00");
            categoryProduct.setProductNum(0);
            categoryProduct.setPrice("0.00");
        }
        Integer totalNum = categoryProduct.getProductNum() + receiptInProduct.getNum();

        Float totalPrice = Float.parseFloat(receiptInProduct.getTotalPrice()) +
                Float.parseFloat(categoryProduct.getTotalPrice());
        DecimalFormat df = new DecimalFormat("0.00");//设置保留位数
        String format = df.format((float) totalPrice / totalNum);

        String totalPrices = df.format(totalPrice);

        Qwert qwert = new Qwert();
        qwert.setBussinessDate(mapper.selectByPrimaryKey(receiptInProduct.getReceiptId()).getBussinessDate());
        qwert.setBeforeNum(categoryProduct.getProductNum());
        qwert.setBeforePrice(categoryProduct.getPrice());
        qwert.setBeforeTotalPrice(categoryProduct.getTotalPrice());
        qwert.setCategoryId(receiptInProduct.getCategoryId());
        qwert.setNumber(receiptInProduct.getNumber());
        qwert.setCtime(DateUtil.now());
        qwert.setCuser(receiptInProduct.getCuser());
        qwert.setProductId(receiptInProduct.getProductId());
        qwert.setNum(receiptInProduct.getNum());
        qwert.setPrice(receiptInProduct.getPrice());
        qwert.setTotalPrice(receiptInProduct.getTotalPrice());
        qwert.setAfterNum(totalNum);
        qwert.setAfterPrice(format);
        qwert.setAfterTotalPrice(totalPrices);
        qwertMapper.insertSelective(qwert);
    }

    /**
     * 加库存
     *
     * @param categoryProduct
     * @param receiptInProduct
     * @throws NumberFormatException
     */
    private synchronized void addNum(CategoryProduct categoryProduct, ReceiptInProduct receiptInProduct) throws NumberFormatException {
        //计算总库存
        Integer totalNum = categoryProduct.getProductNum() + receiptInProduct.getNum();
        categoryProduct.setProductNum(totalNum);
        //计算入库后物品总价
        Float totalPrice = Float.parseFloat(receiptInProduct.getTotalPrice()) +
                Float.parseFloat(categoryProduct.getTotalPrice());
        categoryProduct.setTotalPrice(String.valueOf(totalPrice));
        //计算入库后物品单价
        DecimalFormat df = new DecimalFormat("0.00");//设置保留位数
        String format = df.format((float) totalPrice / totalNum);
        categoryProduct.setPrice(format);
        categoryProductMapper.updateByPrimaryKeySelective(categoryProduct);
    }

    /**
     * 新增
     *
     * @param entity
     * @return
     */
    @Transactional
    public ReceiptIn add(ReceiptIn entity) throws Exception {
        if (categoryMapper.selectByPrimaryKey(entity.getCategoryId()).getIsCheck() == 1) {
            throw new LogicException("仓库在盘点中");
        }
        if (entity.getType() == 1) {
            entity.setNumber("RK" + TimeTool.getTimeDate14());
        } else {
            entity.setNumber("PY" + TimeTool.getTimeDate14());
        }
        mapper.insertSelective(entity);
        //入库单-耗材关联新增
        List<ReceiptInProduct> receiptInProductList = entity.getReceiptInProduct();
        for (ReceiptInProduct receiptInProduct : receiptInProductList) {
            if (receiptInProduct.getPrice().length() > 32) {
                throw new LogicException("单价超出最大长度32位");
            }
            if (receiptInProduct.getTotalPrice().length() > 32) {
                throw new LogicException("总价超出最大长度32位");
            }
            receiptInProduct.setCategoryId(entity.getCategoryId());
            receiptInProduct.setNumber(entity.getNumber());
            receiptInProduct.setCuser(entity.getCuser());
            receiptInProduct.setReceiptId(entity.getId());
            receiptInProductMapper.insertSelective(receiptInProduct);
            //入库单-耗材库存修改
            Example example = new Example(CategoryProduct.class);
            Example.Criteria criteria = example.createCriteria();
            criteria.andEqualTo("categoryId", entity.getCategoryId());
            criteria.andEqualTo("productId", receiptInProduct.getProductId());
            //库存表，不存在新增，存在改数
            List<CategoryProduct> categoryProducts = categoryProductMapper.selectByExample(example);
            if (0 == categoryProducts.size()) {
                CategoryProduct categoryProduct = new CategoryProduct();
                categoryProduct.setCategoryId(entity.getCategoryId());
                categoryProduct.setProductId(receiptInProduct.getProductId());
                categoryProduct.setProductNum(receiptInProduct.getNum());
                if (receiptInProduct.getNum() == 0) {
                    throw new LogicException("请输入入库数量");
                }
                categoryProduct.setPrice(receiptInProduct.getPrice());
                categoryProduct.setTotalPrice(receiptInProduct.getTotalPrice());
                categoryProductMapper.insertSelective(categoryProduct);
                qwertyu(new CategoryProduct(), receiptInProduct);
            } else {
                try {
                    //查询对应库存物品的记录
                    for (CategoryProduct categoryProduct : categoryProducts) {
                        if (categoryProduct.getProductId().equals(receiptInProduct.getProductId())) {
                            qwertyu(categoryProducts.get(0), receiptInProduct);
                            addNum(categoryProducts.get(0), receiptInProduct);
                        }
                    }
                } catch (NumberFormatException e) {
                    log.info("金额格式错误");
                }
            }
        }
        return entity;
    }

    /**
     * 修改
     *
     * @param entity
     * @param flag
     * @return
     * @throws Exception
     */
    @Transactional
    public ReceiptIn edit(ReceiptIn entity, Boolean flag) throws Exception {

        if (categoryMapper.selectByPrimaryKey(entity.getCategoryId()).getIsCheck() == 1) {
            throw new LogicException("仓库在盘点中");
        }
        if (categoryMapper.selectByPrimaryKey(entity.getCategoryId()).getState() != 1) {
            throw new LogicException("仓库不可用");
        }

        //查询原入库单
        ReceiptIn receiptIn = mapper.selectByPrimaryKey(entity.getId());

        //查询原入库单下入库详情
        Example exampleGetReceiptInProduct = new Example(ReceiptInProduct.class);
        Example.Criteria criteriaGetReceiptInProduct = exampleGetReceiptInProduct.createCriteria();
        criteriaGetReceiptInProduct.andEqualTo("receiptId", entity.getId());
        List<ReceiptInProduct> receiptInProductList = receiptInProductMapper.selectByExample(exampleGetReceiptInProduct);
        for (ReceiptInProduct receiptInProduct : receiptInProductList) {
            //查询当前入库单对应入库产品数量
            Integer num = receiptInProduct.getNum();
            //查询当前该产品对应库存记录
            Example example = new Example(CategoryProduct.class);
            Example.Criteria criteria = example.createCriteria();
            criteria.andEqualTo("categoryId", receiptIn.getCategoryId());
            criteria.andEqualTo("productId", receiptInProduct.getProductId());
            List<CategoryProduct> categoryProducts = categoryProductMapper.selectByExample(example);
            CategoryProduct categoryProduct = categoryProducts.get(0);
            //库存量减原入库数量
            categoryProduct.setProductNum(categoryProduct.getProductNum() - receiptInProduct.getNum());
            categoryProductMapper.updateByPrimaryKeySelective(categoryProduct);
            //删除入库详情
            receiptInProductMapper.delete(receiptInProduct);
            //删除qwert
            Example example2 = new Example(Qwert.class);
            Example.Criteria criteria2 = example2.createCriteria();
            criteria2.andEqualTo("productId", receiptInProduct.getProductId());
            criteria2.andEqualTo("number", receiptIn.getNumber());
            qwertMapper.deleteByExample(example2);
        }
        //删除用
        while (flag) {
            mapper.updateByPrimaryKey(entity);
            return entity;
        }
        //删除原入库单
        mapper.deleteByPrimaryKey(entity.getId());

        //新增入库单、入库详情、更新库存量
        entity.setState(1);
        add(entity);
        return entity;
    }

    /**
     * 删除
     *
     * @param entity
     * @return
     * @throws Exception
     */
    @Transactional
    public ReceiptIn del(ReceiptIn entity) throws Exception {
        ReceiptIn receiptIn = mapper.selectByPrimaryKey(entity.getId());
        receiptIn.setState(2);
        edit(receiptIn, true);
        return entity;
    }

    /**
     * 分页查询
     *
     * @param params
     * @return
     */
    public List<ReceiptInGetPageNew> getPages(PageParams<ReceiptInGetPageParams> params) {
        UserManagement user = userManagementMapper.selectByPrimaryKey(params.getParams().getUserId());
        if (user.getDataIsAll() == 1) {
            params.getParams().setIsAdmin(1);
        } else {
            params.getParams().setIsAdmin(2);
        }
        PageHelper.startPage(params.getCurrentPage(), params.getPerPageTotal());
        List<ReceiptInGetPageNew> pageList = mapper.getPage(params.getParams());
        return pageList;
    }

    /**
     * 查看
     *
     * @param id
     * @return
     */
    public ReceiptIn view(String id) {
        ReceiptIn receiptIn = mapper.selectByPrimaryKey(id);
        receiptIn.setCategoryName(categoryMapper.selectByPrimaryKey(receiptIn.getCategoryId()).getName());
        receiptIn.setCuserName(userManagementMapper.selectByPrimaryKey(receiptIn.getCuser()).getName());
        if (StrUtil.isNotBlank(receiptIn.getProvider())) {
            receiptIn.setProviderName(setManagementMapper.selectByPrimaryKey(receiptIn.getProvider()).getName());
        }
        Example example = new Example(ReceiptInProduct.class);
        Example.Criteria criteria = example.createCriteria();
        criteria.andEqualTo("receiptId", id);
        List<ReceiptInProduct> receiptInProductList = receiptInProductMapper.selectByExample(example);
        for (ReceiptInProduct receiptInProduct : receiptInProductList) {
            receiptInProduct.setProduct(productMapper.selectByPrimaryKey(receiptInProduct.getProductId()));
            String price = receiptInProduct.getPrice();
            String totalPrice = receiptInProduct.getTotalPrice();
            BigDecimal db = new BigDecimal(price);
            BigDecimal db1 = new BigDecimal(totalPrice);
            receiptInProduct.setPrice(db.toString());
            receiptInProduct.setTotalPrice(db1.toString());
        }
        receiptIn.setReceiptInProduct(receiptInProductList);
        return receiptIn;
    }

    public List<ReceiptInExtend> print(String ids) {
        List<ReceiptInExtend> list = mapper.selByIds(Arrays.asList(ids.split(",")));
        if (list != null && list.size() > 0) {
            for (ReceiptInExtend extend : list) {
                List<ReceiptMoveProductExtend> receiptMoveProductList = mapper.getReceiptMoveExtend(extend.getId());
                extend.setReceiptMoveProductList(receiptMoveProductList);
            }
        }
        return list;
    }

    public List<ReceiptInGetPage> export(ReceiptInGetPageParams params) {
        UserManagement user = userManagementMapper.selectByPrimaryKey(params.getUserId());
        if (user.getDataIsAll() == 1) {
            params.setIsAdmin(1);
        } else {
            params.setIsAdmin(2);
        }
        List<ReceiptInGetPage> pages = mapper.getPages(params);
        for (ReceiptInGetPage receiptInGetPage : pages) {
            receiptInGetPage.setCategoryName(categoryMapper.selectByPrimaryKey(receiptInGetPage.getCategoryId()).getName());
            receiptInGetPage.setCuserName(userManagementMapper.selectByPrimaryKey(receiptInGetPage.getCuser()).getName());
            if (StrUtil.isNotBlank(receiptInGetPage.getProvider())) {
                receiptInGetPage.setProviderName(setManagementMapper.selectByPrimaryKey(receiptInGetPage.getProvider()).getName());
            }
            receiptInGetPage.setList(mapper.getPageExport(receiptInGetPage.getId()));
            if (receiptInGetPage.getType() == 1) {
                receiptInGetPage.setType1("入库单");
            } else {
                receiptInGetPage.setType1("盘盈入库单");
            }
        }
        return pages;
    }
}
